#!/usr/bin/env python
# -*- coding: utf-8 -*-
#本代码来自所出售产品的淘宝店店主编写
#未经受权不得复制转发
#淘宝店：https://fengmm521.taobao.com/
#再次感谢你购买本店产品
import serial
import serial.tools.list_ports
import os,time
import subprocess
import sys
import platform
sysSystem = platform.system()

serialName = 'USB-SERIAL CH340'

if sysSystem == 'Darwin' or sysSystem == 'Linux':
        serialName = 'USB Serial'

# 获取所有串口设备实例。
# 如果没找到串口设备，则输出：“无串口设备。”
# 如果找到串口设备，则依次输出每个设备对应的串口号和描述信息。

def delaySecend(s):
    print('delay %d secend!'%(s))
    for i in range(s):
        print(s - i)
        time.sleep(1)
def listComPorts():
    ports_list = list(serial.tools.list_ports.comports())
    outs = []
    if len(ports_list) <= 0:
        print("无串口设备。")
    else:
        print("可用的串口设备如下：")
        for comport in ports_list:
            print(list(comport)[0], list(comport)[1])
            outs.append([list(comport)[0],list(comport)[1]])
    return outs
def chickPort(n):
    cstr = 'COM' + str(n)
    plist = listComPorts()
    for i,v in enumerate(plist):
        if v[0] == cstr:
            print('find Port COM%d:'%(n),v)
            return True
    print('not find COM%d'%(n))
    return False

def runCMD(command):
    print(command)
    process = subprocess.Popen(command, stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True, shell=True)

    # 读取并处理命令的标准输出
    while True:
        output_line = process.stdout.readline()
        if not output_line:
            break  # 如果没有更多输出行，则退出循环
        print(output_line.strip())  # 处理输出行，你可以根据需要进行其他操作

    # 等待命令执行完毕
    process.wait()

    # 获取命令的退出码
    return process.returncode
def chickPortName(pname = serialName):
    plist = listComPorts()
    for i,v in enumerate(plist):
        if v[1].find(pname) != -1:
            print(v[0])
            return v[0]
    print('not find:%s'%(pname))
    return None

def is_command_available(command):
    # 获取系统的PATH环境变量
    path_dirs = os.environ["PATH"].split(os.pathsep)

    # 遍历所有的路径，查看命令是否存在于其中
    for path_dir in path_dirs:
        command_path = os.path.join(path_dir, command)
        print(command_path)
        if os.path.isfile(command_path) and os.access(command_path, os.X_OK):
            return True  # 如果命令存在并且可执行，返回True

    return False  # 如果命令不存在，返回False
def getMACAndChipIDWithString(pstr):
    lines = pstr.split('\n')
    cid = None
    macaddr = ''
    for i,v in enumerate(lines):
        if v.find('MAC:') != -1:
            macaddr = v[4:]
        if v.find('ESP32') != -1:
            cid = 'esp32'
        if v.find('ESP8266') != -1:
            cid = 'esp8266'
    return cid,macaddr

def installTool(tool):
    if tool == 'esptool':
        installEsptoolCmd = 'pip install adafruit-ampy -i https://pypi.tuna.tsinghua.edu.cn/simple' 
        # print(installEsptoolCmd)
        runCMD(installEsptoolCmd)
        delaySecend(1)
    elif tool == 'ampy':
        installAmpyCmd = 'pip install adafruit-ampy -i https://pypi.tuna.tsinghua.edu.cn/simple' 
        # print(installAmpyCmd)
        runCMD(installAmpyCmd)
        delaySecend(1)

def getEsptoolName():
    if sysSystem == 'Darwin' or sysSystem == 'Linux':
        cmd = 'esptool.py'
        if is_command_available(cmd):
            return cmd
        else:
            print('mac os not find esptool.py...')
            return
    else:
        return 'esptool.py.exe'
    cmd = 'esptool.exe'
    if is_command_available(cmd):
        print('is heave esptool.exe')
        return cmd
    else:
        cmd = 'esptool.exe.py'
        if is_command_available(cmd):
            print('is heave esptool.exe.py')
            return cmd
        else:
            print('the esptool not heave,please used pip install it!')
    return

def getAMPYToolName():
    if sysSystem == 'Darwin' or sysSystem == 'Linux':
        cmd = 'ampy'
        if is_command_available(cmd):
            return cmd
        else:
            print('mac os not find ampy...')
            return
    else:
        return 'ampy.exe'
    cmd = 'ampy.exe'
    if is_command_available(cmd):
        print('is heave ampy.exe')
        return cmd
    else:
        cmd = 'ampy.exe.py'
        if is_command_available(cmd):
            print('is heave ampy.exe.py')
            return cmd
        else:
            print('the ampy not heave,please used pip install it!')
    return

def saveBoardMacAddr(addr,pth = 'addr.txt'):
    print('add mac addr:%s,to save file:%s'%(addr,pth))
    f = open(pth,'a')
    f.write(addr + '\n')
    f.close()
def getChipID():
    esptool = getEsptoolName()
    if not esptool:
        installTool('esptool')
        esptool = getEsptoolName()
    comnum = chickPortName()
    command = None
    if comnum and esptool:
        command = esptool + ' -p %s run'%(comnum)
    else:
        print('ch340 com port be not heave...')
        return
    # 要运行的命令

    # 使用subprocess运行命令并捕获输出
    try:
        result = subprocess.check_output(command, shell=True, stderr=subprocess.STDOUT, text=True)
        # 将输出保存到文件
        print('-'*10)
        # print(result)
        cid,addr = getMACAndChipIDWithString(result)
        return cid,addr,comnum
    except subprocess.CalledProcessError as e:
        print("命令执行失败。错误消息：", e.output)
        return None,None,None


def main():
    isRun = False
    while True:
        if chickPort(6):
            if not isRun:
                time.sleep(2)
                cmd = 'micropython_all.bat'
                isRun = True
                runCMD(cmd)
            else:
                print('is bren ok,please change board....')
        else:
            isRun = False
        time.sleep(1)

def autoBuren():
    cid,addr,comnum = getChipID()
    if addr:
        saveBoardMacAddr(addr)
    esptool = getEsptoolName()
    burncmd = None
    if esptool and cid:
        cleanflash = esptool + ' -p %s -b 115200 erase_flash'%(comnum)
        runCMD(cleanflash)
        delaySecend(3)
        if cid == 'esp8266':
            burncmd = esptool + " --chip esp8266 --baud 230400 write_flash --flash_size=detect 0 esp8266-espnow-g20-v1.19.1-6-g44f65965b-GENERIC_1M.bin"
        if cid == 'esp32':
            burncmd =esptool + " --chip esp32 --baud 115200 write_flash -z 0x1000 esp32-espnow-g20-v1.19.1-6-g44f65965b-GENERIC.bin"
        runCMD(burncmd)
        delaySecend(3)
        print('start upload micropython py files...')
    else:
        print('not esptool or not find chip id')
        return
    ampytool = getAMPYToolName()
    if not ampytool:
        installTool('ampy')
        ampytool = getAMPYToolName()
    if not ampytool:
        print('ampy tool erro')
        return
def reset():
    cid,addr = getChipID()
    print(cid,addr)

def test():
    portname = chickPortName()
    print('serial-->',portname)
if __name__=="__main__":  
    args = sys.argv
    # if len(args) >= 2:
    #     reset()
    # else:
    #     autoBuren()
    test()